<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>5.函数拥有多个长辈</title>
</head>

<body>
  <script>
    // let hd  = {};
    // js的大多数东西都是对象
    // new String new Number new RegExp

    // 函数本身也是实例化的对象，由new Function()，必然包含__proto__属性，指向 它的构造函数的prototype属性，Function.prototype
    // User.apply() ,函数之所以可以调用apply方法，就是因为它__proto__指向的原型对象实现了apply方法
    console.dir(User.__proto__); //ƒ anonymous() view : ƒ () apply : ƒ apply()
    console.log(User.__proto__ === Function.prototype); //true
    function User () { }
    //console.dir(User);
    /**
    ƒ User():
    prototype : show : ƒ ()
    [[Prototype]] : ƒ () 
    view : ƒ () 
    apply : ƒ apply()
    */
    User.prototype.show = function () {
      console.log("后盾人");
    }
    
    // User 函数实例化一个对象 hd，hd的__proto__对象指向构造函数的原型，也就是 User.prototype
    let hd = new User();
    hd.show();
    console.log(User.prototype == hd.__proto__); //true
    // User.prototype是一个原型对象，一个实例化的对象则包含__proto___属性，指向Object.prototype
    // 因为对象都是由 new Object()实例化而来，Object()是一个函数，就相当于对象的构造方法， 所以会指向Object.prototype，Object.prototype是最顶层的原型，它的__proto___属性是null
    console.log(User.prototype.__proto__ === Object.prototype); //true
    // User 本身 也拥有一个专属的原型对象 __proto__，和 User.prototype 不是同一个
    User.__proto__.view = function () {
      console.log("User function view method");
    };

    User.view();
    console.dir(User);
  </script>
</body>

</html>